﻿using Moq;
using System;
using System.Security.Principal;
using System.Threading;
using System.Web.Mvc;
using WebMatrix.WebData;
using CloudFranceTriple.WebRole;
using Microsoft.VisualStudio.TestTools.UnitTesting;

namespace CloudFranceTriple.Tests
{
    /// <summary>
    /// Purpose is Arrange, no Act, no Assert.
    /// </summary>
    public class UnitTestBase
    {
        protected Mock<ControllerContext> GetControllerContext { get; private set; }
        protected Mock<IWebSecurityWrapper> GetWebSecurity { get; private set; }

        protected String Username { get; private set; }
        protected String Password { get; private set; }
        protected Int32 UserId { get; private set; }
        protected String[] UserRoles { get; private set; }
        protected Boolean RememberMe { get; private set; }

        public static Int32 UnitTestAnnonceId { get; set; }
        public static Int32 UnitTestCategory_ForumId { get { return 53; } }
        public static Int32 UnitTestCategoryId { get; set; }
        public static Int32 UnitTestForumId { get; set; }
        public static Int32 UnitTestPollAnswerId { get; set; }
        public static Int32 UnitTestPollId { get; set; }
        public static Int32 UnitTestPostId { get; set; }
        public static Int32 UnitTestPostId2 { get; set; }
        public static Int32 UnitTestTopicId { get; set; }
        public static Int32 UnitTestPrivateMessageId { get; set; }
        public static Int32 UnitTestPrivateMessageId2 { get; set; }
        public static Int32 UnitTestSecurityForumId { get; set; }
        public static Int32 UnitTestSecurityRoleId { get; set; }
        public static Int32 UnitTestEventCategoryId { get; set; }
        public static Int32 UnitTestEventId { get; set; }
        
        public UnitTestBase()
        {
            // Arrange 

            String _username;
            Int32 _userId;
            String[] _userRoles;

            //_username = String.Empty;
            // _userId = -1;
            // _userRoles = null;

            //_username = "CaptainMagicAA";
            //_userId = 2;
            //_userRoles = new String[1] { "RoleAdminForum" };

            //_username = "Cobaye";
            //_userId = 27;
            //_userRoles = new String[1] { "RoleFans" };

            //_username = "unfan";
            // _userId = 8;
            // _userRoles = new String[1] { "RoleFans" };

            _username = "membre";
            _userId = 9;
            _userRoles = new String[2] { "RoleMember", "RoleAdminForum" };

            //_username = "labaff";
            //_userId = 5;
            //_userRoles = new String[1] { "RoleFans" };

            //_username = "visiteur";
            //_userId = 4;
            //_userRoles = new String[1] { "RoleFans" };

            //_username = "Nouveau";
            //_userId = 12;
            //_userRoles = new String[1] { "RoleFans" };


            var _password = "------";
            var _isAuthenticated = true;
            var _rememberMe = false;

            // Initialize protected properties
            this.Username = _username;
            this.Password = _password;
            this.UserId = _userId;
            this.RememberMe = _rememberMe;
            this.UserRoles = _userRoles;

            var controllerContext = new Mock<ControllerContext>();

            controllerContext.SetupGet(x =>
                x.HttpContext.User.Identity.Name).Returns(_username);

            controllerContext.SetupGet(x =>
                x.HttpContext.User.Identity.IsAuthenticated)
                .Returns(_isAuthenticated);

            controllerContext.SetupGet(x =>
                x.HttpContext.Request.IsAuthenticated)
                .Returns(_isAuthenticated);

            controllerContext.Setup(x => x.HttpContext.User.IsInRole("RoleAdminForum")).Returns(true);

            controllerContext.SetupGet(x => x.HttpContext.Request.UserHostAddress).Returns("::1");

            controllerContext.SetupGet(x => x.HttpContext.Request.Form).Returns(new System.Collections.Specialized.NameValueCollection { { "QuotedPostId", "0" } });

            GetControllerContext = controllerContext;

            var websecurity = new Mock<CloudFranceTriple.WebRole.IWebSecurityWrapper>();
            websecurity.SetupGet(x => x.CurrentUserId).Returns(_userId);
            websecurity.SetupGet(x => x.CurrentUserName).Returns(_username);

            GetWebSecurity = websecurity;

            if (!WebSecurity.Initialized) // Ce test permet d'enchainer plusieurs tests unitaires sans avoir une erreur "Déjà initialisé".
                WebSecurity.InitializeDatabaseConnection("DefaultConnection", "UserProfile", "UserId", "UserName", autoCreateTables: true);

            Thread.CurrentPrincipal = new GenericPrincipal(new GenericIdentity(_username), _userRoles);
        }

        [AssemblyInitialize()]
        public static void AssemblyInit(TestContext context)
        {
        }

        [ClassInitialize()]
        public static void ClassInit(TestContext context)
        {

        }

        [TestInitialize()]
        public void Initialize()
        {

        }

        [TestCleanup()]
        public void Cleanup()
        {

        }

        [ClassCleanup()]
        public static void ClassCleanup()
        {

        }

        [AssemblyCleanup()]
        public static void AssemblyCleanup()
        {

        }

        //[TestMethod]
        //[DataSource("System.Data.OleDb",
        //   "Provider=Microsoft.Jet.OLEDB.4.0;Data Source=\"C:\\sample.mdb\"",
        //   "Table1",
        //   DataAccessMethod.Sequential)]
        //[ExpectedException(typeof(System.DivideByZeroException))]
        //public void UnitTestBase_Test()
        //{
        //Int32 numerator = 4;
        //Int32 denominator = 0;
        //Int32 test = numerator / denominator;
        //}
    }
}
